package leetcode

// Stack Stack is LIFO
type Stack struct {
	top    *node
	length int
}

type node struct {
	value interface{}
	prev  *node
}

//NewStack Create a new stack
func NewStack() *Stack {
	return &Stack{nil, 0}
}

//Len Return the number of items in the stack
func (s *Stack) Len() int {
	return s.length
}

//Peek View the top item on the stack
func (s *Stack) Peek() interface{} {
	if s.length == 0 {
		return nil
	}
	return s.top.value
}

//Pop Pop the top item of the stack and return it
func (s *Stack) Pop() interface{} {
	if s.length == 0 {
		return nil
	}

	n := s.top
	s.top = n.prev
	s.length--
	return n.value
}

// Push a value onto the top of the stack
func (s *Stack) Push(value interface{}) {
	n := &node{value, s.top}
	s.top = n
	s.length++
}

///////////////////////////////////////////////////////////////////////////////////////

type stack struct {
	value []int
}

func newStack() *stack {
	return &stack{
		value: make([]int, 0),
	}
}

func (s *stack) Push(v int) {
	s.value = append(s.value, v)
}

func (s *stack) Len() int {
	l := len(s.value)
	return l
}

func (s *stack) Peek() int {
	l := len(s.value)
	return s.value[l-1]
}

func (s *stack) Pop() {
	l := len(s.value)
	s.value = s.value[:l-1]
}
